﻿using System;
using System.Windows;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using SilverlightViewport.Common;
using Size=System.Windows.Size;

namespace SilverlightViewport.WPF
{
    public class WriteableBitmapRenderer : RasterRendererElement
    {
        private WriteableBitmap m_writeableBitmap;
        private IntPtr m_pBackBuffer;
        private Size m_lastImageSize;

        private void InitializeRenderBitmap(int width, int height)
        {
            m_writeableBitmap = new WriteableBitmap(width, height, 96, 96, PixelFormats.Bgra32, null);
            m_pBackBuffer = m_writeableBitmap.BackBuffer;
            RenderedImage.Source = m_writeableBitmap;
            m_lastImageSize = new Size(width, height);
        }

        public override void RenderFrame(RenderedFrameEventArgs frameArgs)
        {
            int width = frameArgs.Width;
            int height = frameArgs.Height;

            if (m_writeableBitmap == null)
            {
                Dispatcher.BeginInvoke((Action)(() => InitializeRenderBitmap(width, height)));
                return;
            }

            if (m_lastImageSize.Height != height || m_lastImageSize.Width != width)
            {
                Dispatcher.BeginInvoke((Action)(() => InitializeRenderBitmap(width, height)));
                return;
            }
          
            CopyMemory(m_pBackBuffer, frameArgs.Buffer, frameArgs.BufferSize);

            Dispatcher.Invoke((Action)delegate
            {
                m_writeableBitmap.Lock();
                m_writeableBitmap.AddDirtyRect(new Int32Rect(0, 0, width, height));
                m_writeableBitmap.Unlock();
            });
        }
    }
}
